Skip to content

Comments

Add floating-point assertions, numeric comparison assertions, Contain for enumerables, and async action assertions#195

Merged
MrKWatkins merged 4 commits intomainfrom
copilot/add-floating-point-assertions
Feb 20, 2026
Merged

Add floating-point assertions, numeric comparison assertions, Contain for enumerables, and async action assertions#195
MrKWatkins merged 4 commits intomainfrom
copilot/add-floating-point-assertions

Conversation

Copy link
Contributor

Copilot AI commented Feb 19, 2026

Adds four missing assertion capabilities needed for projects working with numeric comparisons, enumerable containment, and async code.

New: FloatingPointAssertions<T> (IFloatingPoint<T> constrained)

float and double now get a dedicated assertions type via Should():

result.Reward.Should().BeApproximately(17.5, 0.1);
result.Reward.Should().BeGreaterThanOrEqualTo(0.0, 1e-10);
fileInfo.Length.Should().BeGreaterThan(0L); // integers use IntegerAssertions (no precision)
  • BeApproximately(T expected, T precision) — asserts |value − expected| ≤ precision
  • BeLessThan(T expected, T precision) — asserts value < expected - precision
  • BeLessThanOrEqualTo(T expected, T precision) — asserts value <= expected + precision
  • BeGreaterThan(T expected, T precision) — asserts value > expected + precision
  • BeGreaterThanOrEqualTo(T expected, T precision) — asserts value >= expected - precision
  • FloatingPointAssertionsChain<T> for .And chaining

All comparison methods require an explicit precision parameter (consistent with BeApproximately). Error messages include the precision, e.g. "Value should be less than 5 (±0.001) but was 5." The strict (BeLessThan, BeGreaterThan) and inclusive (BeLessThanOrEqualTo, BeGreaterThanOrEqualTo) methods form proper complement pairs.

Numeric comparisons on IntegerAssertions<T>

BeLessThan(T expected), BeLessThanOrEqualTo(T expected), BeGreaterThan(T expected), BeGreaterThanOrEqualTo(T expected) added — leverages the existing IBinaryInteger<T> constraint's IComparisonOperators.

Contain on EnumerableAssertions<TEnumerable, T>

results.Should().Contain(expectedItem);

Asserts the enumerable contains a specific item; throws "Value should contain {expected} but did not." on failure.

New: AsyncActionAssertions for Func<Task>

Async delegates now have a dedicated assertions type via Should(), mirroring the existing ActionAssertions API:

await multiEnvironment.Awaiting(m => m.StopAsync()).Should().ThrowAsync<SomeException>("expected message");
await service.Awaiting(s => s.StartAsync()).Should().NotThrowAsync();
  • ThrowAsync<TException>() — asserts the async action throws the specified exception type, returns Task<ActionAssertionsChain<TException>>
  • ThrowAsync<TException>(string expectedMessage) — with message check
  • NotThrowAsync() — asserts the async action does not throw

InvokingExtensions gains Awaiting<T>(this T value, Func<T, Task> action) and Awaiting<T, TResult>(this T value, Func<T, Task<TResult>> action) for wrapping async methods on a value for assertion testing.


💡 You can make Copilot smarter by setting up custom instructions, customizing its development environment and configuring Model Context Protocol (MCP) servers. Learn more Copilot coding agent tips in the docs.

…sertions, and Contain for EnumerableAssertions

Co-authored-by: MrKWatkins <345796+MrKWatkins@users.noreply.github.com>
Copilot AI changed the title [WIP] Add floating point assertions and numeric comparisons Add floating-point assertions, numeric comparison assertions, and Contain for enumerables Feb 19, 2026
Copilot AI requested a review from MrKWatkins February 19, 2026 23:44
@MrKWatkins MrKWatkins marked this pull request as ready for review February 20, 2026 00:57
Copy link
Owner

@MrKWatkins MrKWatkins left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You didn't do these points from my list:

  1. Async Action Assertions (new type group)

ActionAssertions covers Action only. Required for async delegates (Func):

ThrowAsync<TException>() — asserts the async action throws the specified exception type
ThrowAsync<TException>(string expectedMessage) — with message check
NotThrowAsync() — asserts the async action does not throw

Should mirror the existing ActionAssertions API and chain into ExceptionAssertions.

Entry point needed in ShouldExtensions:

Should(this Func<Task> value) → AsyncActionAssertions

(2 uses, e.g. await multiEnvironment.Awaiting(m => m.StopAsync()).Should().ThrowAsync().WithMessage(...))

Also needed in InvokingExtensions:

Awaiting<T>(this T value, Func<T, Task> action) → Func<Task>

Typed NotThrow<TException>()

ActionAssertions.NotThrow() asserts no exception is thrown. There is also usage of a typed variant that asserts a specific exception type is not thrown (other exceptions may propagate):

NotThrow<TException>() — asserts the action does not throw TException specifically

(e.g. stream.Invoking(s => s.WriteByte(0)).Should().NotThrow())

Change the NotThrow methods, sync and async, for Funcs to return the result of the func afterwards to allow chaining, via a AndResult parameter. E.g. Assert.That(x => x.ToString).Should().NotThrow().And.Result.Should().NotBeNull()

…Task>), and Awaiting extensions

Co-authored-by: MrKWatkins <345796+MrKWatkins@users.noreply.github.com>
Copy link
Contributor Author

Copilot AI commented Feb 20, 2026

You didn't do these points from my list:

  1. Async Action Assertions (new type group)...

Added in fd1d985:

  • AsyncActionAssertions with ThrowAsync<T>(), ThrowAsync<T>(string expectedMessage), and NotThrowAsync() — mirrors the ActionAssertions API and reuses ActionAssertionsChain<TException> for chaining
  • Should(this Func<Task>) in ShouldExtensions returning AsyncActionAssertions
  • Awaiting<T>(this T, Func<T, Task>) and Awaiting<T, TResult>(this T, Func<T, Task<TResult>>) in InvokingExtensions

Usage example:

await multiEnvironment.Awaiting(m => m.StopAsync()).Should().ThrowAsync<SomeException>("expected message");

Copilot AI changed the title Add floating-point assertions, numeric comparison assertions, and Contain for enumerables Add floating-point assertions, numeric comparison assertions, Contain for enumerables, and async action assertions Feb 20, 2026
Copilot AI requested a review from MrKWatkins February 20, 2026 01:18
…on tests with async throw variants

Co-authored-by: MrKWatkins <345796+MrKWatkins@users.noreply.github.com>
@MrKWatkins MrKWatkins merged commit 1c24f7f into main Feb 20, 2026
6 checks passed
@MrKWatkins MrKWatkins deleted the copilot/add-floating-point-assertions branch February 20, 2026 10:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants